package ar.edu.utn.frba.dds.tp.ui;


import org.uqbar.arena.actions.MessageSend;
import org.uqbar.arena.bindings.NotNullObservable;
import org.uqbar.arena.layout.ColumnLayout;
import org.uqbar.arena.layout.HorizontalLayout;
import org.uqbar.arena.widgets.Button;
import org.uqbar.arena.widgets.Label;
import org.uqbar.arena.widgets.Panel;
import org.uqbar.arena.widgets.TextBox;
import org.uqbar.arena.widgets.tables.Column;
import org.uqbar.arena.widgets.tables.Table;
import org.uqbar.arena.windows.SimpleWindow;
import org.uqbar.arena.windows.WindowOwner;

import ar.edu.utn.frba.dds.tp.code.Asientos.AsientoDeVuelo;
import ar.edu.utn.frba.dds.tp.code.usuarios.UsuarioStandard;
import ar.edu.utn.frba.dds.tp.code.vuelos.ExistingReservationException;
import ar.edu.utn.frba.dds.tp.code.vuelos.TransactionCouldntSucceedException;
import ar.edu.utn.frba.dds.tp.transformers.ClaseTransformer;
import ar.edu.utn.frba.dds.tp.transformers.PrecioTransformer;
import ar.edu.utn.frba.dds.tp.transformers.StringToFechaTransformer;
import ar.edu.utn.frba.dds.tp.transformers.StringToLugarTransformer;
import ar.edu.utn.frba.dds.tp.transformers.UbicacionTransformer;
import ar.edu.utn.frba.dds.tp.ui.appModel.BusquedasManager;

public class BuscarWindow extends SimpleWindow<BusquedasManager>{
	
	private static final long serialVersionUID = -3716467432356280555L;
	
	UsuarioStandard user;
	
	public BuscarWindow(WindowOwner parent, BusquedasManager model, UsuarioStandard user) {
		super(parent, model);
		this.user = user;
	}

	public UsuarioStandard getUser(){
		return this.user;
	}
	
	@Override
	protected void addActions(Panel panel) {

		this.createOptionButtons(panel);
	}

	@Override
	protected void createFormPanel(Panel panel) {
		this.setTitle("Buscar Vuelos");
		
		this.createInputFields(panel);
		
		this.createSearchPanel(panel);
		
		this.createResultsGrid(panel);
		
	}

	protected void createResultsGrid(Panel panel) {
		
		Table<AsientoDeVuelo> table = new Table<AsientoDeVuelo>(panel, AsientoDeVuelo.class);
		table.setHeigth(200);
		table.setWidth(450);

		table.bindItemsToProperty("resultados");
		table.bindValueToProperty("asientoSeleccionado");

		this.describeResultsGrid(table);
	}
	

	private void describeResultsGrid(Table<AsientoDeVuelo> table) {
		
		this.createColumn(table, "Aerolinea",30,"aerolinea");
		
		this.createColumn(table, "Vuelo", 20, "codigoDeVuelo");
		
		this.createColumn(table, "Asiento", 20, "numeroDeAsiento");
		
		this.createColumn(table, "Precio", 40, "precio")
			.bindContentsToTransformer(new PrecioTransformer());
		
		this.createColumn(table, "Ubicacion", 40, "ubicacion")
			.bindContentsToTransformer(new UbicacionTransformer());

		this.createColumn(table, "Clase", 40, "clase")
			.bindContentsToTransformer(new ClaseTransformer());
		
	}
	
	private Column<AsientoDeVuelo> createColumn (Table<AsientoDeVuelo> table, String title,
												 int pixels, String propertyToBind){
		return new Column<AsientoDeVuelo>(table)
					.setTitle(title)
					.bindContentsToProperty(propertyToBind);
	}
	
	private void createSearchPanel(Panel panel){
		Panel buscar_panel = new Panel(panel).setLayout(new HorizontalLayout());
		this.createSearchButton(buscar_panel);
	}
	
	private void createSearchButton(Panel panel) {
				
		this.createButton(panel, "Buscar", this.getModelObject(), "buscarVuelos")
			.disableOnError();
		this.createButton(panel, "Limpiar", this.getModelObject(), "clear");
	}
	
	private void createInputFields(Panel panel){
		Panel input_panel = new Panel(panel).setLayout(new ColumnLayout(4));
		
		new Label(input_panel).setText("Origen: ");
		new TextBox(input_panel)
			.bindValueToProperty("origen")
			.setTransformer(new StringToLugarTransformer()); 
		
		new Label(input_panel).setText("Destino: ");
		new TextBox(input_panel)
			.bindValueToProperty("destino")
			.setTransformer(new StringToLugarTransformer()); 
		
		new Label(input_panel).setText("Fecha: ");
		new TextBox(input_panel)
			.bindValueToProperty("fecha")
			.setTransformer(new StringToFechaTransformer() );
			
	}
	
	private void createOptionButtons(Panel panel){
		Panel button_panel = new Panel(panel).setLayout(new HorizontalLayout());
		
		Button comprar = this.createButton(button_panel, "Comprar", this, "comprarAsiento");
		Button reservar = this.createButton(button_panel, "Reservar", this, "reservarAsiento");
		this.createButton(button_panel, "Cerrar", this, "close");
		
		// Deshabilitar los botones si no hay ningún elemento seleccionado en la grilla.
		NotNullObservable elementSelected = new NotNullObservable("asientoSeleccionado");
		comprar.bindEnabled(elementSelected);
		reservar.bindEnabled(elementSelected);
	}
	
	private Button createButton(Panel panel, String caption, Object target, String methodName){
		
			return new Button(panel)
					.setCaption(caption)
					.onClick(new MessageSend(target, methodName));
	}
	
	public void comprarAsiento(){
		try{ 
			this.user.comprarAsiento(this.getModelObject().getAsientoSeleccionado());
			new AccionConcretadaWindow(getOwner(), this).open();
		}
		catch(TransactionCouldntSucceedException e){
			new AccionErroneaWindow(getOwner(), this, e.getMessage(), "compra").open();
		}
	}
		
	public void reservarAsiento(){
		try{ 
			this.user.reservarAsiento(this.getModelObject().getAsientoSeleccionado());
			new AccionConcretadaWindow(getOwner(), this).open();
		}
		catch(TransactionCouldntSucceedException e){
			new AccionErroneaWindow(getOwner(), this, e.getMessage(), "reserva").open();
		}
		catch(ExistingReservationException e){
			new AccionSobreReservarWindow(getOwner(),this).open();
		}
	}
	
}
